package gui;

import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.geom.AffineTransform;
import java.awt.image.BufferedImage;
import java.awt.print.PageFormat;
import java.awt.print.Printable;
import javax.swing.Timer;

/**
 *
 * @author Quân
 */
public class SingleImageShower extends javax.swing.JPanel implements ActionListener, Printable {

    Timer timer = null;
    private BufferedImage image = null;
    double scale = 0;
    double theta = 0;
    double delta = 0;
    double step = 50;
    int count = 0;

    public void addTheta(double theta) {
        if (timer == null) {
            timer = new Timer(5, this);
        }
        if (0 < count && count < step) {
            return;
        }

        count = 0;
        delta = theta / step;
        timer.start();
    }

    public BufferedImage getImage() {
        return image;
    }

    public void setImage(BufferedImage image) {
        this.image = image;
        scale = 0;
        theta = 0;
        this.updateUI();
    }

    /**
     * Creates new form SingleImageShower
     */
    public SingleImageShower() {
        initComponents();
    }

    public void Zoom(int a) {
        if (scale == 0) {
            scale = 1;
        }
        scale = scale * (1f - 0.1f * a);
        this.updateUI();
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        if (image != null) {
            Graphics2D g2 = (Graphics2D) g;
            int w = getWidth();
            int h = getHeight();
            int imageWidth = image.getWidth();
            int imageHeight = image.getHeight();

            if (scale == 0f) {
                int max = Math.max(imageHeight, imageWidth);
                if (max <= w) {
                    scale = 1;
                } else {
                    scale = (double) w / max;
                }
            }

            double x = (w - scale * imageWidth) / 2;
            double y = (h - scale * imageHeight) / 2;
            AffineTransform at = AffineTransform.getTranslateInstance(x, y);
            at.scale(scale, scale);
            at.rotate(theta, imageWidth / 2, imageHeight / 2);
            g2.drawRenderedImage(image, at);
        }
    }

    /**
     * This method is called from within the constructor to initialize the form.
     * WARNING: Do NOT modify this code. The content of this method is always
     * regenerated by the Form Editor.
     */
    @SuppressWarnings("unchecked")
    // <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
    private void initComponents() {

        setBorder(javax.swing.BorderFactory.createLineBorder(new java.awt.Color(0, 0, 0)));

        javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this);
        this.setLayout(layout);
        layout.setHorizontalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 398, Short.MAX_VALUE)
        );
        layout.setVerticalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 298, Short.MAX_VALUE)
        );
    }// </editor-fold>//GEN-END:initComponents
    // Variables declaration - do not modify//GEN-BEGIN:variables
    // End of variables declaration//GEN-END:variables

    @Override
    public void actionPerformed(ActionEvent e) {
        this.theta += delta;
        this.repaint();
        if (++count == step) {
            timer.stop();
        }
    }

    @Override
    public int print(Graphics g, PageFormat pf, int pageIndex) {
        Graphics2D g2d = (Graphics2D) g;
        g.translate((int) (pf.getImageableX()), (int) (pf.getImageableY()));
        if (pageIndex == 0) {
            double pageWidth = pf.getImageableWidth();
            double pageHeight = pf.getImageableHeight();
            double imageWidth = this.image.getWidth();
            double imageHeight = this.image.getHeight();
            double scaleX = pageWidth / imageWidth;
            double scaleY = pageHeight / imageHeight;
            double scaleFactor = Math.min(scaleX, scaleY);
            g2d.scale(scaleFactor, scaleFactor);
            g.drawImage(this.image, 0, 0, null);
            return Printable.PAGE_EXISTS;
        }
        return Printable.NO_SUCH_PAGE;
    }
}
